package online.inote.naruto.api.access.admin.modules.system.service;

import com.alibaba.fastjson.JSON;
import online.inote.naruto.api.access.admin.modules.system.entity.ManagerEntity;
import online.inote.naruto.api.access.admin.modules.system.entity.SystemEntity;
import online.inote.naruto.api.access.admin.modules.system.repository.ManagerRepository;
import online.inote.naruto.api.access.props.ApiAccessProperties;
import online.inote.naruto.cache.CacheSupport;
import online.inote.naruto.exception.NormalOperationException;
import online.inote.naruto.utils.StringUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import java.util.UUID;
import java.util.stream.Collectors;

/**
 * @description 系统管理人Service
 * @author XQF.Sui
 * @date 2021/07/27 18:22
 */
@Service
@Transactional(rollbackFor = RuntimeException.class)
public class ManagerService {

  private final ManagerRepository repository;
  private final ApiAccessProperties apiProps;

  public ManagerService(ManagerRepository repository, ApiAccessProperties apiProps) {
    this.repository = repository;
    this.apiProps = apiProps;
  }

  /**
   * 根据系统ID查询管理人信息
   *
   * @param systemId 系统ID
   * @return 管理人信息
   */
  public ManagerEntity getBySystemId(String systemId) {
    String managerInfo = CacheSupport.get(apiProps.getCache().initManagerCacheKey(systemId));

    if (StringUtils.isBlank(managerInfo) && apiProps.getDatabase().getEnable()) {
      return repository.findBySystemId(systemId);
    }

    if (StringUtils.isBlank(managerInfo)) {
      return null;
    }

    return JSON.parseObject(managerInfo, ManagerEntity.class);
  }

  /**
   * 保存
   *
   * @param system 服务信息
   */
  public void save(SystemEntity system) {
    ManagerEntity manager = system.getManager();
    manager.setSystemId(system.getId());

    if (StringUtils.isBlank(manager.getId())) {
      manager.setId(UUID.randomUUID().toString());
    }

    manager.genSignatureDigest();

    if (apiProps.getDatabase().getEnable()) {
      repository.save(manager);
    }

    CacheSupport.cache(
        apiProps.getCache().initManagerCacheKey(manager.getId()), JSON.toJSONString(manager));
  }

  public List<ManagerEntity> getManagerBySystemIdList(List<String> systemIdList) {
    // 查缓存
    List<ManagerEntity> managerEntities = getCacheManagerBySystemIdList(systemIdList);

    if (!CollectionUtils.isEmpty(managerEntities)) {
      List<String> cacheSystemIdList =
          managerEntities.stream().map(ManagerEntity::getSystemId).collect(Collectors.toList());

      boolean result = systemIdList.removeAll(cacheSystemIdList);

      if (result) {
        throw new NormalOperationException("缓存ID删除失败");
      }

      if (!CollectionUtils.isEmpty(systemIdList)) {
        List<ManagerEntity> dbManagerEntities = repository.findBySystemIdIn(systemIdList);

        if (!CollectionUtils.isEmpty(dbManagerEntities)) {
          managerEntities.addAll(dbManagerEntities);
        }
      }
    } else {
      managerEntities = repository.findBySystemIdIn(systemIdList);
    }

    return managerEntities;
  }

  private List<ManagerEntity> getCacheManagerBySystemIdList(List<String> systemIdList) {
    Set<ManagerEntity> managerSet =
        systemIdList.stream()
            .map(
                id ->
                    JSON.parseObject(
                        CacheSupport.get(apiProps.getCache().initManagerCacheKey(id)),
                        ManagerEntity.class))
            .collect(Collectors.toSet());

    if (!CollectionUtils.isEmpty(managerSet)) {
      managerSet.remove(null);
    }

    return new ArrayList<>(managerSet);
  }
}
